/*
 * bcti_dta_new.h
 *
 *  Created on: 2011-3-22
 *      Author: li.zhaoping
 */

#ifndef BCTI_DTA_H__
#define BCTI_DTA_H__




/* base type define*/
typedef signed char int8_dta;
typedef unsigned char uint8_dta;
typedef short int int16_dta;
typedef unsigned short int uint16_dta;
typedef int int32_dta;
typedef unsigned int uint32_dta;
typedef long long int64_dta;
typedef unsigned long long uint64_dta;
typedef int32_dta bcti_dta_handle;

/*
 * 负数表示必须处理的错误
 */
typedef enum {
	BCTI_DTA_STATUS_READERROR = -6, //读错误
	BCTI_DTA_STATUS_NOTOPENED = -5, //未打开播放
	BCTI_DTA_STATUS_NOTINITED = -4, //未初始化
	BCTI_DTA_STATUS_READALLEND = -3, //读完所有数据
	BCTI_DTA_STATUS_READPARTEND = -2, //读完其中一段视频数据
	BCTI_DTA_STATUS_FAILURE = -1, //通用失败
	BCTI_DTA_STATUS_SUCCESS = 0, //成功
	BCTI_DTA_STATUS_ALREADYINIT, //重复初始化
	BCTI_DTA_STATUS_ALREADYOPEN, //重复打开播放
	BCTI_DTA_STATUS_BUFFERING, //缓冲中
	BCTI_DTA_STATUS_NOTSUPPORT, //不支持该功能
	BCTI_DTA_STATUS_RESERVED,
//保留

} bcti_dta_status_e;

typedef enum {
	BCTI_DTA_ERR_NONE = 0, //无错误
	BCTI_DTA_ERR_RESERVED, //保留
	BCTI_DTA_ERR_NETFAIL = 3, //网络错误
	BCTI_DTA_ERR_SERVERFAIL,
//服务器错误

} bcti_dta_err_e;

typedef enum {
	BCTI_DTA_READ_ERR = -1, //错误
	BCTI_DTA_READ_SUC = 0, //成功 非下面的情况
	BCTI_DTA_READ_SUC_FILEEND = 1, //读完一个
	BCTI_DTA_READ_SUC_ALLEND = 2,//所有数据读完
	BCTI_DTA_READ_SUC_CLIPEND = 3,//clips模式中，其中一个clip读完

} bcti_dta_read_e;


typedef enum {
	BCTI_DTA_SEEKTIME_ERR = -1, //出错
	BCTI_DTA_SEEKTIME_FAIL = 0, //播放器要自己做seek（直接调SeekBySize）
	BCTI_DTA_SEEKTIME_SUC_TOPOS = 2, //Dta转化时间到Pos，并通过参数返回该Pos，播放器通过该Pos进行seek
	BCTI_DTA_SEEKTIME_SUC_TOREOPEN = 3,//Dta转化后获取到的是一个新的文件，播放器需要重新codec过程

} bcti_dta_seek_e;

typedef enum {

	BCTI_DTA_SERVER_TIMEOUT = 0, // 0,  连接服务器超时,停止播放
	BCTI_DTA_NO_SERVER, // 1,  找不到服务器,停止播放
	BCTI_DTA_SERVER_NO_RESPONSE, // 2,  服务器未响应,停止播放
	BCTI_DTA_SERVER_INVALID, // 3,  解析服务器域名失败.
	BCTI_DTA_VERSION_LOW, // 4,  客户端版本号太低,退出网络
	BCTI_DTA_CLIENT_NAME, // 5,  客户端名称或引用页不正确,退出播放
	BCTI_DTA_URL_INVALID, // 6,  播放的文件不存在或网址错误
	BCTI_DTA_NO_SERVICE, // 7,  服务不存在,停止播放
	BCTI_DTA_OUT_OF_SERVICE, // 8,  不在服务区.
	BCTI_DTA_MEDIA_INFO_ERROR, // 9,  媒体信息加载时错误..
	BCTI_DTA_INDEX_INFO_ERROR, // 10, 媒体索引信息错误
	BCTI_DTA_NO_INDEX, // 11, 没有获取到媒体索引信息,不能拖动播放位置
	BCTI_DTA_NO_MEIDIA, // 12, 找不到媒体
	BCTI_DTA_MULTI_INSTANCE, // 13, 请确定是否有另一个实例正在播放此文件
	BCTI_DTA_PREPARE_MEDIA_INFO, // 14, 正在准备媒体信息
	BCTI_DTA_GETTING_MEDIA_INFO, // 15, 正在获取媒体信息
	BCTI_DTA_GETTING_INDEX_INFO, // 16, 正在获取媒体索引信息
	BCTI_DTA_PLAYING, // 17, 正在播放
	BCTI_DTA_BUFFERING, // 18, 正在缓冲数据  [param1为缓冲百分比0 - 100]
	BCTI_DTA_CONNECTING, // 19, 正在连入网络
	BCTI_DTA_MEDIA_READY, // 20, 准备媒体就绪
	BCTI_DTA_PARSING_SERVER, // 21, 正在解析服务器域名..
	BCTI_DTA_GET_MEDIA_INFO, // 22, 已成功获取到媒体信息.
	BCTI_DTA_BUFFERED, // 23, 数据缓冲完毕.[param1为100]
	BCTI_DTA_PREPARE_MEDIA, // 24, 准备媒体
	BCTI_DTA_STORAGE_ERROR, // 25. 访问存储器失败
	BCTI_DTA_QUIT, // 26. 程序退出

	BCTI_DTA_DATA_TIMEOUT, // 27, 等待数据超时

	BCTI_DTA_UPDATING, // 28, 正在升级
	BCTI_DTA_UPDATE_FAILED, // 29, 升级失败
	BCTI_DTA_UPDATE_OK, // 30, 升级成功
	BCTI_DTA_AUTH_UNPASSED, // 31, 验证成功，非付费用户
	BCTI_DTA_AUTH_PASSED, // 32, 验证成功，付费用户
	BCTI_DTA_AUTH_INVALID, // 33, 单部点播，验证未通过
	BCTI_DTA_AUTH_FAILED, // 34, 验证失败
	BCTI_DTA_ALLOCATE_PGF,
// 35, 预先分配缓存文件空间失败

} bcti_dta_event_e;

/* 回调函数类型
 * handle 		[播放过程的句柄，即CreateSession返回的句柄]
 * id 				[事件id，参考bcti_dta_event_e类型]
 * param1 		[根据id的不同而不同]
 * param2 		[根据id的不同而不同]
 * message 	[事件提示信息,可能会为NULL]
 * 备注			param1和param2的值请参考bcti_dta_event_e的注释，如无说明，默认为0
 */
typedef int32_dta (*bcti_dta_event_handler)(bcti_dta_handle handle,
		bcti_dta_event_e id, uint32_dta param1, uint32_dta param2,
		const char* message);

typedef enum {
	DTA_SEEK_BEGIN,//从文件头
	DTA_SEEK_CURR,//从当前位置
	DTA_SEEK_END,//从文件尾，此时offset应该为负数

} bcti_dta_seek_direction_e;

/*
 * 该bcti_movie_info类型可根据播放器能力不同进行微调
 */
typedef struct {
	int count;

} bcti_movie_info;


typedef enum{
	CLIPTYPE_NONE = 0,
	CLIPTYPE_AD,
	CLIPTYPE_MV,

}ClipType_e;

//单个切片文件信息
typedef struct segMentInfo{
		int				   duration;//时间长度，单位毫秒
		long long	   length; //长度，单位字节

}segInfo_t;


/* bcti_clip_info
 * segCount以及segList只在ClipType_e为CLIPTYPE_MV，且bClip为true时有效，否则都为0
 */
typedef struct {
	bool 							seekAble; //能否seek
	long long	   				length; //总长度，单位字节
	ClipType_e				    clipType; //ClipType_e
	int				   				duration;//总时间长度，单位毫秒
	bool				   			bClip; //是否是切片
	int								segCount;//切片个数
	segInfo_t*					segList;//segInfo_t数组指针

} bcti_clip_info;


class CBctiDta {
public:
	static const char* 				GetVesion();
	static CBctiDta* 					GetInstance();

	/* Init
	 * [功能] 初始化
	 * [备注] work_dir不能为空
	 * [返回值] BCTI_DTA_STATUS_SUCCESS：成功
	 * 			  BCTI_DTA_STATUS_FAILURE： 出错
	 */
	virtual bcti_dta_status_e 	Init(const char *work_dir) = 0;

	/* DeInit
	 * [功能] 反初始化
	 * [备注]  调用该函数之后不能再调其它函数，除非重新Init
	 * [返回值] BCTI_DTA_STATUS_SUCCESS：成功
	 * 			  BCTI_DTA_STATUS_FAILURE： 出错
	 */
	virtual bcti_dta_status_e 	DeInit() = 0;

	/* SetEventHandler
	 * [功能] 设置消息回调函数
	 * [备注]  只用和Init一起调用一次即可
	 * [返回值] BCTI_DTA_STATUS_SUCCESS：成功
	 * 			  BCTI_DTA_STATUS_FAILURE： 出错
	 */
	virtual bcti_dta_status_e 	SetEventHandler(bcti_dta_event_handler event_handler) = 0;

	/* Open
	 * [功能] 打开一个播放链接
	 * [备注]  url不能为空，并且函数会阻塞到获取文件长度才返回
	 * [返回值] BCTI_DTA_STATUS_SUCCESS：成功
	 * 			  BCTI_DTA_STATUS_FAILURE：  出错
	 */
	virtual bcti_dta_status_e 	Open(const char *url) = 0;

	/* Close
	 * [功能] 关闭一个播放链接
	 * [备注]  可异步调用该函数来打断open的阻塞
	 * [返回值] BCTI_DTA_STATUS_SUCCESS：成功
	 * 			  BCTI_DTA_STATUS_FAILURE：  出错
	 */
	virtual bcti_dta_status_e 	Close() = 0;

	/* NextClip
	 * [功能] 判断是否还有下一视频未播放并移动读指针到新视频上
	 * [返回值] true：还有视频未读取
	 * 			  false：视频已完全读取
	 */
	virtual bool 						NextClip() = 0;

	/* Read
	 * [功能] 读取数据
	 * [参数] segment_index ：只在切片模式下，指示当前读到的切片段的索引，size单位字节
	 * [返回值] BCTI_DTA_READ_SUC：数据正常读取
	 * 			  BCTI_DTA_READ_SUC_FILEEND：数据正常读取，但是已读完该片段视频，下次调用将是新视频的数据，播放器应该在得到该值后开始重置
	 * 			  BCTI_DTA_READ_SUC_ALLEND：数据正常读取，而且已读完该所有视频
	 * 			  BCTI_DTA_READ_SUC_CLIPEND：切片模式下，一个切片段读完
	 * 			  BCTI_DTA_READ_ERR：出错
	 */
	virtual bcti_dta_read_e 		Read(char* buffer, int64_dta *size, int* segment_index) = 0;

	/* SeekByTime
	 * [功能] 用于判断UI指定的time offset是否需要额外处理
	 * [参数] time_offset：要定位的时间，单位毫秒
	 * 			toPos：DTA转化时间到长度的输出值，单位字节
	 * 			time_offset_inner：切片模式下，跨段seek后位于新切片段的偏移时间，单位毫秒
	 * 			segment_index：切片模式下，跨段seek后位于新切片段的索引
	 * [备注] 播放器不支持切片的，可以不考虑time_offset_inner和segment_index
	 * 			toPos用于播放器不能timeSeek的情况，由Dta来做时间转化的工作
	 * [返回值] BCTI_DTA_SEEKTIME_FAIL：播放器要自己做seek；请注意，如果支持切片模式，如果segment_index>=0,则
	 * 													 segment_index为跨切片段的索引，time_offset_inner为定位到新的切片段的时间偏移
	 * 			  BCTI_DTA_SEEKTIME_SUC_TOPOS：Dta转化时间到Pos，并通过参数返回该Pos，播放器通过该Pos进行seek
	 * 			  BCTI_DTA_SEEKTIME_SUC_TOREOPEN：Dta转化后获取到的是一个新的文件，播放器需要重新codec过程
	 * 			  BCTI_DTA_SEEKTIME_ERR：出错
	 */
	virtual bcti_dta_seek_e 		SeekByTime(unsigned long time_offset,
																long long* toPos,
																unsigned long *time_offset_inner,
																int *segment_index) = 0;

	/* SeekBySize
	 * [功能] 根据长度进行定位
	 * [参数] off会返回实际定位的pos，单位字节
	 * [返回值] BCTI_DTA_STATUS_SUCCESS：成功
	 * 			  BCTI_DTA_STATUS_FAILURE： 出错
	 */
	virtual bcti_dta_status_e 	SeekBySize(bcti_dta_seek_direction_e from, int64_dta *off) = 0;

	/* CurrentFileLength
	 * [功能] 获取当前视频的长度，请注意一次播放请求可能会对应几个视频的播放，
	 * 			在NextClip返回true之后，请再次调用此函数获取新视频的长度
	 * [备注] 该结果实际也包含在GetClipContext中
	 * [返回值] 大于0为文件长度，单位字节
	 * 			  -1： 出错
	 */
	virtual long long 				CurrentFileLength() = 0;

	/* Percent
	 * [功能] 获取当前视频下载缓冲的百分比
	 * [备注] 如果链接打开失败，函数返回0
	 * [返回值] 缓冲的百分比
	 */

	virtual unsigned int 			Percent() = 0;


	/* GetClipContext
	 * [功能] 获取当前播放视频的信息，如是否能seek，长度
	 * [备注] 也可以直接用CurrentFileLength获取长度；
	 * [返回值] BCTI_DTA_STATUS_SUCCESS：成功
	 * 			  BCTI_DTA_STATUS_FAILURE： 出错
	 */
	virtual bcti_dta_status_e 	GetClipContext(int clip_index,bcti_clip_info* clip_info) = 0;

	/* GetMovieContext
	 * [功能] 获取整个播放过程的信息
	 * [返回值] BCTI_DTA_STATUS_SUCCESS：成功
	 * 			  BCTI_DTA_STATUS_FAILURE： 出错
	 */
	virtual bcti_dta_status_e 	GetMovieContext(bcti_movie_info* movie_info) = 0;

	/* Cancle
	 * TODO(lzp):未启用
	 */
	virtual bcti_dta_status_e 	Cancle() = 0;

	/* GetSplashTime
	 * TODO(lzp):未启用
	 */
	virtual unsigned int 			GetSplashTime(int segment_index) = 0;

	/* CurrentFileTime
	 * TODO(lzp):未启用
	 */
	virtual unsigned int 			CurrentFileTime() = 0;

#if 1

	/* ~CBctiDta
	 * For samsung
	 * 析构函数
	 */
	virtual ~CBctiDta(){};


#endif

};

#endif	// BCTI_DTA_H__
